package gradle.rabbit.common.config;

import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.core.AcknowledgeMode;
import org.springframework.amqp.rabbit.config.SimpleRabbitListenerContainerFactory;
import org.springframework.amqp.rabbit.connection.CachingConnectionFactory;
import org.springframework.amqp.rabbit.connection.ConnectionFactory;
import org.springframework.amqp.rabbit.connection.RabbitConnectionFactoryBean;
import org.springframework.amqp.rabbit.core.RabbitAdmin;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
import org.springframework.retry.support.RetryTemplate;

import java.util.Objects;


/**
 * BaseRabbitConnectionFactory
 *
 * @author 1141193930@qq.com
 */
@Slf4j
public class BaseRabbitConnectionFactory {


    /**
     * 获取工厂配置Bean
     *
     * @param sslEnabled                是否启用SSL支持
     * @param verifyHostname            是否启用主机名验证
     * @param validateServerCertificate 是否启用服务器端证书验证
     * @return {@link RabbitConnectionFactoryBean}
     */
    public static RabbitConnectionFactoryBean getConnectionFactoryBean(boolean sslEnabled, boolean verifyHostname, boolean validateServerCertificate) {
        if (sslEnabled) {
            // 启用SSL配置
            RabbitConnectionFactoryBean factoryBean = new RabbitConnectionFactoryBean();
            // 是否使用SSL连接
            factoryBean.setUseSSL(true);
            // 是否启用主机名验证
            factoryBean.setEnableHostnameVerification(verifyHostname);
            // 是否跳过服务器证书验证 true = 跳过｜false = 验证
            factoryBean.setSkipServerCertificateValidation(!validateServerCertificate);
            factoryBean.afterPropertiesSet();
            return factoryBean;
        }
        return null;
    }


    /**
     * 获取连接工厂
     *
     * @param factoryBean 工厂Bean
     * @return {@link CachingConnectionFactory}
     */
    public static CachingConnectionFactory getCacheConnectionFactory(RabbitConnectionFactoryBean factoryBean) {
        try {
            if (Objects.nonNull(factoryBean) && Objects.nonNull(factoryBean.getObject())) {
                return new CachingConnectionFactory(factoryBean.getObject());
            }
            return new CachingConnectionFactory();
        } catch (Exception e) {
            log.error("【BaseRabbitConnectionFactory】获取连接工厂失败，Message = {}", e.getMessage());
            throw new RuntimeException(e);
        }
    }


    /**
     * 构造RabbitTemplate模版
     *
     * @param connectionFactory 连接工厂
     * @return {@link RabbitTemplate}
     */
    public static RabbitTemplate getRabbitTemplate(boolean retryEnabled, ConnectionFactory connectionFactory) {
        RabbitTemplate rabbitTemplate = new RabbitTemplate(connectionFactory);
        if (retryEnabled) {
            rabbitTemplate.setRetryTemplate(new RetryTemplate());
        }
        return rabbitTemplate;
    }


    /**
     * 构造消费者容器工厂
     *
     * @param connectionFactory 连接工厂
     * @return {@link SimpleRabbitListenerContainerFactory}
     */
    public static SimpleRabbitListenerContainerFactory getRabbitListenerContainer(ConnectionFactory connectionFactory) {
        SimpleRabbitListenerContainerFactory containerFactory = new SimpleRabbitListenerContainerFactory();
        // 设置消费者ACK消息的模式，默认是自动，此处设置为手动
        containerFactory.setAcknowledgeMode(AcknowledgeMode.MANUAL);
        containerFactory.setConnectionFactory(connectionFactory);
        containerFactory.setRetryTemplate(new RetryTemplate());
        return containerFactory;
    }

    /**
     * 构造批量处理消费者容器工厂
     *
     * @param connectionFactory 连接工厂
     * @return {@link SimpleRabbitListenerContainerFactory}
     */
    public static SimpleRabbitListenerContainerFactory getBatchRabbitListenerContainer(ConnectionFactory connectionFactory) {
        SimpleRabbitListenerContainerFactory containerFactory = new SimpleRabbitListenerContainerFactory();
        // 设置消费者ACK消息的模式，默认是自动，此处设置为手动
        containerFactory.setAcknowledgeMode(AcknowledgeMode.MANUAL);
        containerFactory.setConnectionFactory(connectionFactory);
        containerFactory.setRetryTemplate(new RetryTemplate());
        //设置批量监听
        containerFactory.setBatchListener(true);
        containerFactory.setConsumerBatchEnabled(true);
        containerFactory.setBatchSize(80);
        return containerFactory;
    }

    /**
     * 构造随附单据批量处理消费者容器工厂
     *
     * @param connectionFactory 连接工厂
     * @return {@link SimpleRabbitListenerContainerFactory}
     */
    public static SimpleRabbitListenerContainerFactory getAccompanyingDocumentsBatchRabbitListenerContainer(ConnectionFactory connectionFactory) {
        SimpleRabbitListenerContainerFactory containerFactory = new SimpleRabbitListenerContainerFactory();
        // 设置消费者ACK消息的模式，默认是自动，此处设置为手动
        containerFactory.setAcknowledgeMode(AcknowledgeMode.MANUAL);
        containerFactory.setConnectionFactory(connectionFactory);
        containerFactory.setRetryTemplate(new RetryTemplate());
        //设置批量监听
        containerFactory.setBatchListener(true);
        containerFactory.setConsumerBatchEnabled(true);
        containerFactory.setBatchSize(3);
        return containerFactory;
    }


    /**
     * 构造RabbitAdmin
     *
     * @param connectionFactory 连接工厂
     * @return {@link RabbitAdmin}
     */
    public static RabbitAdmin getRabbitAdmin(ConnectionFactory connectionFactory) {
        return new RabbitAdmin(connectionFactory);
    }
}
